package com.ruibang.glass.purchase.service.impl;


import com.baomidou.mybatisplus.core.metadata.IPage;
import com.baomidou.mybatisplus.core.toolkit.CollectionUtils;
import com.baomidou.mybatisplus.core.toolkit.StringUtils;
import com.baomidou.mybatisplus.core.toolkit.Wrappers;
import com.baomidou.mybatisplus.extension.plugins.pagination.Page;
import com.baomidou.mybatisplus.extension.service.impl.ServiceImpl;
import com.ruibang.glass.common.constants.Constants;
import com.ruibang.glass.common.constants.RedisKey;
import com.ruibang.glass.common.domain.camunda.BpmProcessInstanceCreate;
import com.ruibang.glass.common.domain.camunda.BpmProcessInstanceStatus;
import com.ruibang.glass.common.domain.camunda.BpmTaskApproveReq;
import com.ruibang.glass.common.domain.file.FileBusiness;
import com.ruibang.glass.common.domain.file.FileInfo;
import com.ruibang.glass.common.domain.material.MaterialManagement;
import com.ruibang.glass.frequencycontrol.annotation.RedissonLock;
import com.ruibang.glass.purchase.constant.PurchaseErrorCode;
import com.ruibang.glass.purchase.domain.req.PurchaseApprovalReq;
import com.ruibang.glass.purchase.domain.req.PurchaseDullnessReq;
import com.ruibang.glass.purchase.entity.*;
import com.ruibang.glass.purchase.feign.CamundaApi;
import com.ruibang.glass.purchase.feign.FileApi;
import com.ruibang.glass.purchase.feign.MaterialApi;
import com.ruibang.glass.purchase.mapper.*;
import com.ruibang.glass.purchase.service.CommonService;
import com.ruibang.glass.purchase.service.PurchaseApprovalItemsService;
import com.ruibang.glass.purchase.service.PurchaseApprovalListService;
import com.ruibang.glass.purchase.service.PurchaseApprovalSupplierService;
import com.teaming.cloud.framework2.autoconfigure.redis.RedisSingleService;
import com.teaming.cloud.framework2.common.constant.CommonConstant;
import com.teaming.cloud.framework2.common.exception.ServiceException;
import com.teaming.cloud.framework2.common.model.ResultBody;
import org.springframework.beans.BeanUtils;
import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.stereotype.Service;
import org.springframework.transaction.annotation.Transactional;

import java.io.Serializable;
import java.math.BigDecimal;
import java.time.LocalDate;
import java.time.format.DateTimeFormatter;
import java.util.*;
import java.util.stream.Collectors;

import static com.ruibang.glass.common.constants.Constants.FINISH_NODE_KEY;

/**
 * <p>
 * 采购审批列表 服务实现类
 * </p>
 *
 * @author mameng
 * @since 2024-04-17
 */
@Service
public class PurchaseApprovalListServiceImpl extends ServiceImpl<PurchaseApprovalListMapper, PurchaseApprovalList> implements PurchaseApprovalListService {

    @Autowired
    private CamundaApi camundaApi;

    @Autowired
    private PurchaseApprovalItemsService purchaseApprovalItemsService;

    @Autowired
    private PurchaseApprovalSupplierService purchaseApprovalSupplierService;

    @Autowired
    private RedisSingleService redisService;

    @Autowired
    private CommonService commonService;

    @Autowired
    private FileApi fileApi;

    @Autowired
    private PurchaseContractsMapper purchaseContractsMapper;

    @Autowired
    private PurchaseContractProductsMapper purchaseContractProductsMapper;

    @Autowired
    private PurchaseOrderDetailsMapper purchaseOrderDetailsMapper;

    @Autowired
    private PurchaseOrderDetailSupplierMapper purchaseOrderDetailSupplierMapper;

    @Autowired
    private PurchaseRelatedProductMapper purchaseRelatedProductMapper;

    @Autowired
    private PurchaseApplicationListMapper purchaseApplicationListMapper;

    @Autowired
    private PurchaseBidEvaluationReportsMapper evaluationReportsMapper;

    @Autowired
    private MaterialApi materialApi;

    private final String nodeName = "采购专员";

    private final String PURCHASE_APPROVE_NUMBER = "purchase_approve_number";

    /**
     * 订单审批和立项审批走同一个流程
     *
     * @param purchaseApprovalList
     */
    @Override
    public void addPurchaseApprovalList(PurchaseApprovalList purchaseApprovalList) {
        baseMapper.insert(purchaseApprovalList);
        //保存比价单文件
        if (CollectionUtils.isNotEmpty(purchaseApprovalList.getPriceFileIds())) {
            FileBusiness fileBusiness = new FileBusiness();
            fileBusiness.setBusinessId(purchaseApprovalList.getId());
            fileBusiness.setFileIds(purchaseApprovalList.getPriceFileIds());
            fileBusiness.setAttribute(com.ruibang.glass.purchase.constant.Constants.PRICE_FILE);
            fileApi.updateBusinessById(fileBusiness);
        }
        //插入数据到采购审批采购物品详情表
        if (CollectionUtils.isNotEmpty(purchaseApprovalList.getPurchaseApprovalItemsList())) {
            for (PurchaseApprovalItems purchaseApprovalItems : purchaseApprovalList.getPurchaseApprovalItemsList()) {
                purchaseApprovalItems.setPurchaseApprovalId(purchaseApprovalList.getId());
            }
            purchaseApprovalItemsService.saveBatch(purchaseApprovalList.getPurchaseApprovalItemsList());
        }
        //插入数据到采购审批供应商信息表
        if (CollectionUtils.isNotEmpty(purchaseApprovalList.getPurchaseApprovalSupplierList())) {
            for (PurchaseApprovalSupplier purchaseApprovalSupplier : purchaseApprovalList.getPurchaseApprovalSupplierList()) {
                purchaseApprovalSupplier.setIsUsed(CommonConstant.ZERO_STR);
                purchaseApprovalSupplier.setPurchaseApprovalId(purchaseApprovalList.getId());
            }
            purchaseApprovalSupplierService.saveBatch(purchaseApprovalList.getPurchaseApprovalSupplierList());
        }

        if (CommonConstant.ONE_STR.equals(purchaseApprovalList.getSpStatus())) {
            //保存附件信息
            if (CollectionUtils.isNotEmpty(purchaseApprovalList.getFileIds())) {
                //根据文件Id列表查询文件信息，获取相关文件
                ResultBody<List<FileInfo>> result = fileApi.getFileInfoByFileIds(purchaseApprovalList.getFileIds());
                if (result != null && CollectionUtils.isNotEmpty(result.getData())) {
                    //上传文件
                    List<FileInfo> fileInfos = result.getData();
                    for (FileInfo fileInfo : fileInfos) {
                        fileInfo.setBusinessId(purchaseApprovalList.getId());
                        fileInfo.setAttribute(com.ruibang.glass.purchase.constant.Constants.ATTACHMENT);
                        fileInfo.setFileId(null);
                    }
                    fileApi.saveInfo(fileInfos);
                }
            }
        } else {
            //保存附件信息
            if (CollectionUtils.isNotEmpty(purchaseApprovalList.getFileIds())) {
                FileBusiness fileBusiness = new FileBusiness();
                fileBusiness.setFileIds(purchaseApprovalList.getFileIds());
                fileBusiness.setBusinessId(purchaseApprovalList.getId());
                fileBusiness.setAttribute(com.ruibang.glass.purchase.constant.Constants.ATTACHMENT);
                fileApi.updateBusinessById(fileBusiness);
            }
        }
    }

    @Override
    public void approveProject(BpmProcessInstanceCreate bpmProcessInstanceCreate) {
        Map<String, Object> variables = new HashMap<>();
        String userId = commonService.getUser().getUserId();
        variables.put(Constants.PROCESS_INSTANCE_STARTER_USER_ID, userId);
        variables.put(Constants.PROCESS_INSTANCE_BUSINESS_KEY, bpmProcessInstanceCreate.getBusinessKey());
        variables.put(Constants.PROCESS_INSTANCE_MENU_ID, bpmProcessInstanceCreate.getMenuId());
        bpmProcessInstanceCreate.setVariables(variables);
        String processId = commonService.startProcess(bpmProcessInstanceCreate);
        if (StringUtils.isNotBlank(processId)) {
            BpmTaskApproveReq bpmTaskApproveReq = new BpmTaskApproveReq();
            bpmTaskApproveReq.setId(processId);
            bpmTaskApproveReq.setUserId(userId);
            camundaApi.approve(bpmTaskApproveReq);
        }
    }

    @Override
    public void processNotice(String businessId) {
        ResultBody<List<BpmProcessInstanceStatus>> resultBody = camundaApi.queryProcessInstanceStatus(Arrays.asList(businessId));
        if (resultBody != null && CollectionUtils.isNotEmpty(resultBody.getData())) {
            BpmProcessInstanceStatus process = resultBody.getData().get(0);
            if (process.getNodeKey().equals(FINISH_NODE_KEY)) {
                PurchaseApprovalList purchaseApproval = baseMapper.selectById(businessId);
                if (purchaseApproval != null) {
                    purchaseApproval.setIsFinished(CommonConstant.ONE_STR);
                    this.updateById(purchaseApproval);
                    if (CommonConstant.TWO_STR.equals(purchaseApproval.getSpStatus())) {
                        //采购订单 流程无关联合同
                        PurchaseOrderDetails purchaseOrderDetails = new PurchaseOrderDetails();
                        purchaseOrderDetails.setPurchaseOrderNumber(purchaseApproval.getNumber());
                        PurchaseContracts purchaseContracts = purchaseContractsMapper.selectById(purchaseApproval.getContractId());
                        if (purchaseContracts != null) {
                            purchaseOrderDetails.setProjectName(purchaseApproval.getProjectName());
                            purchaseOrderDetails.setProjectNumber(purchaseApproval.getNumber());
                            purchaseOrderDetails.setSupplierName(purchaseApproval.getSupplierName());
                            purchaseOrderDetails.setSupplierId(purchaseApproval.getSupplierId());
                            purchaseOrderDetails.setContractId(purchaseApproval.getContractId());
                            purchaseOrderDetails.setContractNumber(purchaseContracts.getContractNumber());
                            purchaseOrderDetails.setOrderStatus(CommonConstant.ONE_STR);
                            purchaseOrderDetails.setApplicant(purchaseApproval.getApplicant());
                            purchaseOrderDetails.setApplicantId(purchaseApproval.getApplicantId());
                            purchaseOrderDetails.setDeptId(purchaseApproval.getDeptId());
                            purchaseOrderDetails.setDeptName(purchaseApproval.getDeptName());
                            purchaseOrderDetails.setApplicationTime(purchaseApproval.getApplyTime());
                            purchaseOrderDetails.setPayStatus(CommonConstant.TWO_STR);
                            purchaseOrderDetailsMapper.insert(purchaseOrderDetails);
                            List<PurchaseApprovalItems> items = purchaseApprovalItemsService.list(Wrappers.<PurchaseApprovalItems>lambdaQuery().eq(PurchaseApprovalItems::getPurchaseApprovalId, purchaseApproval.getId()));
                            if (CollectionUtils.isNotEmpty(items)) {
                                List<String> itemIds = items.stream().map(PurchaseApprovalItems::getItemId).collect(Collectors.toList());
                                //List<PurchaseRelatedProduct> purchaseRelatedProductList = new ArrayList<>();
                                Map<String, String> itemTypeMap = null;
                                if (CollectionUtils.isNotEmpty(itemIds)) {
                                    ResultBody<List<MaterialManagement>> materialRs = materialApi.getMaterialManagerByIds(itemIds);
                                    if (materialRs != null && CollectionUtils.isNotEmpty(materialRs.getData())) {
                                        itemTypeMap = materialRs.getData().stream().collect(Collectors.toMap(MaterialManagement::getId, MaterialManagement::getWarehouseCode, (m1, m2) -> m1));
                                    }
                                }
                                for (PurchaseApprovalItems item : items) {
                                    PurchaseRelatedProduct product = new PurchaseRelatedProduct();
                                    BeanUtils.copyProperties(item, product);
                                    product.setDetailId(purchaseOrderDetails.getId());
                                    product.setInitQuantity(item.getQuantity());
                                    product.setId(null);
                                    if (itemTypeMap != null) {
                                        String itemType = itemTypeMap.get(item.getItemId());
                                        if (StringUtils.isNotBlank(itemType)) {
                                            product.setItemType(itemType);
                                        }
                                    }
                                    purchaseRelatedProductMapper.insert(product);
                                }
                            }

                        }
                    }
                }
            }
        }
    }

    @Override
    public String getSequenceNumber() {
        return baseMapper.getSequenceNumber();
    }

    @Override
    public IPage<PurchaseApprovalList> queryPage(PurchaseApprovalReq purchaseApprovalReq) {

        IPage<PurchaseApprovalList> approvalPage = baseMapper.queryPage(new Page<>(purchaseApprovalReq.getPageNo(), purchaseApprovalReq.getPageSize()), purchaseApprovalReq);

        if (approvalPage == null || CollectionUtils.isEmpty(approvalPage.getRecords())) {
            return new Page<>(purchaseApprovalReq.getPageNo(), purchaseApprovalReq.getPageSize());
        }

        Map<Object, Object> userMap = redisService.hmget(RedisKey.USER_GROUP_TYPE);
        List<String> businessKeys = approvalPage.getRecords().stream().map(PurchaseApprovalList::getId).collect(Collectors.toList());
        Map<String, BpmProcessInstanceStatus> processMap = null;
        //获取业务流程状态
        ResultBody<List<BpmProcessInstanceStatus>> resultBody = camundaApi.queryProcessInstanceStatus(businessKeys);
        if (resultBody != null && CollectionUtils.isNotEmpty(resultBody.getData())) {
            processMap = resultBody.getData().stream().collect(Collectors.toMap(bp -> bp.getBusinessKey(), bp -> bp, (bp1, bp2) -> bp1));
        }
        Map<String, String> purchaseContractMap = getPurchaseContractMap(businessKeys);
        for (PurchaseApprovalList purchaseApprovalList : approvalPage.getRecords()) {
            if (processMap != null && processMap.get(purchaseApprovalList.getId()) != null) {
                BpmProcessInstanceStatus status = processMap.get(purchaseApprovalList.getId());
                purchaseApprovalList.setProcessId(status.getProcessInstanceId());
                purchaseApprovalList.setNodeName(status.getNodeName());
                if (StringUtils.isNotBlank(status.getUserId())) {
                    if (status.getUserId().indexOf(CommonConstant.SpecialSign.COMMA.getName()) != -1) {
                        String[] userIds = status.getUserId().split(CommonConstant.SpecialSign.COMMA.getName());
                        StringBuilder userName = new StringBuilder();
                        int size = userIds.length;
                        for (int i = 0; i < size; i++) {
                            String name = userMap.get(userIds[i]) == null ? "" : userMap.get(userIds[i]).toString();
                            if (i == size - 1) {
                                userName.append(name);
                            } else {
                                userName.append(name).append(CommonConstant.SpecialSign.COMMA.getName());
                            }
                        }
                        purchaseApprovalList.setApproveUserId(status.getUserId());
                        purchaseApprovalList.setApproveUser(userName.toString());
                    } else {
                        purchaseApprovalList.setApproveUserId(status.getUserId());
                        purchaseApprovalList.setApproveUser(userMap.get(status.getUserId()) == null ? "" : userMap.get(status.getUserId()).toString());
                    }

                }
            }

            //校验 审批是否可以发起流程
            if (purchaseApprovalList.getSpStatus().equals(Constants.ONE_STR)) {
                if (purchaseContractMap.get(purchaseApprovalList.getId()) == null) {
                    purchaseApprovalList.setContractStatus(Constants.ONE_STR);
                }
                if (purchaseContractMap.get(purchaseApprovalList.getId()) == null) {
                    purchaseApprovalList.setContractStatus(Constants.TWO_STR);
                }
            } else {
                if (purchaseContractMap.get(purchaseApprovalList.getId()) == null) {
                    purchaseApprovalList.setContractStatus(Constants.TWO_STR);
                }
            }
        }
        return approvalPage;
    }


    @Override
    public PurchaseApprovalList getInfoByNumber(String number) {
        PurchaseApprovalList purchaseApprovalList = baseMapper.selectOne(lambdaQuery().getWrapper().eq(PurchaseApprovalList::getNumber, number));
        if (purchaseApprovalList != null) {
            ResultBody<List<String>> resultBody = fileApi.getFileIdsByBusinessId(purchaseApprovalList.getId());
            if (resultBody != null && CollectionUtils.isNotEmpty(resultBody.getData())) {
                purchaseApprovalList.setFileIds(resultBody.getData());
            }

            if (purchaseApprovalList != null && StringUtils.isNotBlank(purchaseApprovalList.getApplyNumber())) {
                PurchaseApplicationList purchaseApplication = purchaseApplicationListMapper.getByNumber(purchaseApprovalList.getApplyNumber());
                if (purchaseApplication != null) {
                    purchaseApprovalList.setProjectIntroduce(purchaseApplication.getIntroduction());
                }
            }
            List<PurchaseApprovalSupplier> list = purchaseApprovalSupplierService.list(Wrappers.<PurchaseApprovalSupplier>lambdaQuery().eq(PurchaseApprovalSupplier::getPurchaseApprovalId, purchaseApprovalList.getId()));
            List<ProcureReportBidders> reportBidders = evaluationReportsMapper.getByProjectNumber(purchaseApprovalList.getNumber());
            List<PurchaseApprovalItems> items = purchaseApprovalItemsService.list(Wrappers.<PurchaseApprovalItems>lambdaQuery().eq(PurchaseApprovalItems::getPurchaseApprovalId, purchaseApprovalList.getId()));
            Map<String, String> winBiddMap = new HashMap<>();
            if (CollectionUtils.isNotEmpty(reportBidders)) {
                winBiddMap = reportBidders.stream().collect(Collectors.toMap(ProcureReportBidders::getBidderId, ProcureReportBidders::getIsWinningBid, (p1, p2) -> p1));
            }
            if (winBiddMap != null) {
                for (PurchaseApprovalSupplier approvalSupplier : list) {
                    if(!(CommonConstant.THREE_STR.equals(purchaseApprovalList.getSpStatus()) && CollectionUtils.isEmpty(items))){
                        approvalSupplier.setIsWinningBid(winBiddMap.get(approvalSupplier.getSupplierId())==null?"0":winBiddMap.get(approvalSupplier.getSupplierId()));
                    }
                }
            }
            purchaseApprovalList.setPurchaseApprovalSupplierList(list);

            if(CollectionUtils.isNotEmpty(items)){
                String contractId = purchaseContractsMapper.getByProjectNumber(number);
                List<PurchaseApprovalItems> newItems = new ArrayList<>();
                if(StringUtils.isNotBlank(contractId)){
                    List<PurchaseContractProducts> contractProducts = purchaseContractProductsMapper.selectList(Wrappers.<PurchaseContractProducts>lambdaQuery().eq(PurchaseContractProducts::getContractId,contractId));
                    if(CollectionUtils.isNotEmpty(contractProducts)){
                        Map<String,Double> productMap = contractProducts.stream().filter(p->p.getQuantity()!=null).collect(Collectors.toMap(PurchaseContractProducts::getProductId,PurchaseContractProducts::getQuantity,(p1,p2)->p1));
                        for (PurchaseApprovalItems item : items) {
                            Double quality = productMap.get(item.getItemId());
                            if(quality!=null&&quality>0){
                                if(item.getQuantity()>quality){
                                    item.setQuantity(item.getQuantity()-quality);
                                    newItems.add(item);
                                }
                            }else{
                                newItems.add(item);
                            }
                        }
                        purchaseApprovalList.setPurchaseApprovalItemsList(newItems);
                    }else{
                        purchaseApprovalList.setPurchaseApprovalItemsList(items);
                    }
                }else{
                    purchaseApprovalList.setPurchaseApprovalItemsList(items);
                }
            }

        }
        return purchaseApprovalList;
    }


    /**
     * 校验 流程是否有订单
     *
     * @param ids
     * @return
     */
    public Map<String, String> getPurchaseContractMap(List<String> ids) {
        List<PurchaseContracts> gPurchaseContractsList = purchaseContractsMapper.selectList(Wrappers.<PurchaseContracts>lambdaQuery().select(PurchaseContracts::getId, PurchaseContracts::getApproveId)
                .in(PurchaseContracts::getApproveId, ids));
        Map<String, String> getPurchaseContractMap = new HashMap<>();
        for (PurchaseContracts gPurchaseContracts : gPurchaseContractsList) {
            if (StringUtils.isNotEmpty(gPurchaseContracts.getApproveId())) {
                getPurchaseContractMap.put(gPurchaseContracts.getApproveId(), gPurchaseContracts.getId());
            }
        }
        return getPurchaseContractMap;
    }

    /**
     * 跟新时跟新审批 流程并且生成订单数据
     * 跟新总额
     *
     * @param purchaseApprovalList
     */

    @Override
    @Transactional(rollbackFor = Exception.class)
    public void updatePurchaseApprovalList(PurchaseApprovalList purchaseApprovalList) {
        Map<String, String> approveStatusMap = null;
        ResultBody<List<BpmProcessInstanceStatus>> resultBody = camundaApi.queryProcessInstanceStatus(Arrays.asList(purchaseApprovalList.getId()));
        if (resultBody != null && CollectionUtils.isNotEmpty(resultBody.getData())) {
            approveStatusMap = resultBody.getData().stream().collect(Collectors.toMap(BpmProcessInstanceStatus::getBusinessKey, BpmProcessInstanceStatus::getResult, (s1, s2) -> s1));
        }

        if (CollectionUtils.isNotEmpty(purchaseApprovalList.getPurchaseApprovalItemsList())) {
            List<PurchaseRequestItems> requestItems = baseMapper.queryByApplyNumber(purchaseApprovalList.getApplyNumber());
            Map<String, Double> requestQualityMap = null;
            if (CollectionUtils.isNotEmpty(requestItems)) {
                requestQualityMap = requestItems.stream().collect(Collectors.toMap(PurchaseRequestItems::getItemCode, PurchaseRequestItems::getQuantity, (p1, p2) -> p2));
            }
            for (PurchaseApprovalItems items : purchaseApprovalList.getPurchaseApprovalItemsList()) {
                if (CommonConstant.TWO_STR.equals(purchaseApprovalList.getSpStatus())) {
                    if (items.getQuantity() == null
                            || items.getTaxInclusiveUnitPrice() == null
                            || items.getQuantity().equals(BigDecimal.ZERO)
                            || items.getTaxInclusiveUnitPrice() == null
                    ) {
                        throw new ServiceException(PurchaseErrorCode.NOT_NO_OR_NULL.getCode(), PurchaseErrorCode.NOT_NO_OR_NULL.getMsg());
                    }
                }

                if (requestQualityMap != null) {
                    Double oldQuality = requestQualityMap.get(items.getItemCode());
                    if (oldQuality != null && (items.getQuantity() > oldQuality || items.getQuantity() < 1)) {
                        throw new ServiceException(PurchaseErrorCode.QUALITY_IS_MORE_THAN_REQUEST.getCode(), PurchaseErrorCode.QUALITY_IS_MORE_THAN_REQUEST.getMsg());
                    }
                }
            }

        } else {
            if (CommonConstant.TWO_STR.equals(purchaseApprovalList.getSpStatus())) {
                if (CollectionUtils.isEmpty(purchaseApprovalList.getPurchaseApprovalItemsList())) {
                    throw new ServiceException(PurchaseErrorCode.NOT_NO_PRODUCT.getCode(), PurchaseErrorCode.NOT_NO_PRODUCT.getMsg());
                }
            }
        }


        if (approveStatusMap != null && approveStatusMap.get(purchaseApprovalList.getId()) != null) {
            purchaseApprovalList.setApproveStatus(approveStatusMap.get(purchaseApprovalList.getId()).toString());
        }

        baseMapper.updateById(purchaseApprovalList);

        fileApi.deleteByBusinessId(purchaseApprovalList.getId());
        //附件
        if (CollectionUtils.isNotEmpty(purchaseApprovalList.getFileIds())) {
            FileBusiness fileBusiness = new FileBusiness();
            fileBusiness.setFileIds(purchaseApprovalList.getFileIds());
            fileBusiness.setBusinessId(purchaseApprovalList.getId());
            fileBusiness.setAttribute(com.ruibang.glass.purchase.constant.Constants.ATTACHMENT);
            fileApi.updateBusinessById(fileBusiness);
        }
        //比价单文件
        if (CollectionUtils.isNotEmpty(purchaseApprovalList.getPriceFileIds())) {
            FileBusiness fileBusiness = new FileBusiness();
            fileBusiness.setFileIds(purchaseApprovalList.getPriceFileIds());
            fileBusiness.setBusinessId(purchaseApprovalList.getId());
            fileBusiness.setAttribute(com.ruibang.glass.purchase.constant.Constants.PRICE_FILE);
            fileApi.updateBusinessById(fileBusiness);
        }
        purchaseApprovalItemsService.remove(Wrappers.<PurchaseApprovalItems>lambdaQuery().eq(PurchaseApprovalItems::getPurchaseApprovalId, purchaseApprovalList.getId()));
        purchaseApprovalSupplierService.remove(Wrappers.<PurchaseApprovalSupplier>lambdaQuery().eq(PurchaseApprovalSupplier::getPurchaseApprovalId, purchaseApprovalList.getId()));
        if (CollectionUtils.isNotEmpty(purchaseApprovalList.getPurchaseApprovalSupplierList())) {
            for (PurchaseApprovalSupplier purchaseApprovalItems : purchaseApprovalList.getPurchaseApprovalSupplierList()) {
                purchaseApprovalItems.setPurchaseApprovalId(purchaseApprovalList.getId());
                purchaseApprovalSupplierService.save(purchaseApprovalItems);
            }
        }
        if (CollectionUtils.isNotEmpty(purchaseApprovalList.getPurchaseApprovalItemsList())) {
            for (PurchaseApprovalItems purchaseApprovalItems : purchaseApprovalList.getPurchaseApprovalItemsList()) {
                purchaseApprovalItems.setPurchaseApprovalId(purchaseApprovalList.getId());
                purchaseApprovalItemsService.save(purchaseApprovalItems);
            }
        }
    }

    /**
     * 详情
     *
     * @param id
     * @return
     */
    @Override
    public PurchaseApprovalList getPurchaseApprovalList(String id) {
        PurchaseApprovalList purchaseApprovalList = baseMapper.selectById(id);
        ResultBody<List<FileBusiness>> resultBody = fileApi.getFileBusinessByIds(Collections.singletonList(id));
        if (resultBody != null && CollectionUtils.isNotEmpty(resultBody.getData())) {
            List<FileBusiness> fileData = resultBody.getData();
            List<String> fileIds = new ArrayList<>();
            List<String> priceFileIds = new ArrayList<>();
            if (CollectionUtils.isNotEmpty(fileData)) {
                for (FileBusiness fileDatum : fileData) {
                    if (com.ruibang.glass.purchase.constant.Constants.PRICE_FILE.equals(fileDatum.getAttribute())) {
                        priceFileIds.addAll(fileDatum.getFileIds());
                    } else {
                        fileIds.addAll(fileDatum.getFileIds());
                    }
                }
            }
            //获取附件
            purchaseApprovalList.setFileIds(fileIds);
            //获取比价单文件
            purchaseApprovalList.setPriceFileIds(priceFileIds);
        }

        if (purchaseApprovalList != null && StringUtils.isNotBlank(purchaseApprovalList.getApplyNumber())) {
            PurchaseApplicationList purchaseApplication = purchaseApplicationListMapper.getByNumber(purchaseApprovalList.getApplyNumber());
            if (purchaseApplication != null) {
                purchaseApprovalList.setProjectIntroduce(purchaseApplication.getIntroduction());
            }
        }

        List<PurchaseApprovalSupplier> list = purchaseApprovalSupplierService.list(Wrappers.<PurchaseApprovalSupplier>lambdaQuery().eq(PurchaseApprovalSupplier::getPurchaseApprovalId, id));
        purchaseApprovalList.setPurchaseApprovalSupplierList(list);
        List<PurchaseApprovalItems> list1 = purchaseApprovalItemsService.list(Wrappers.<PurchaseApprovalItems>lambdaQuery().eq(PurchaseApprovalItems::getPurchaseApprovalId, id));
        purchaseApprovalList.setPurchaseApprovalItemsList(list1);
        return purchaseApprovalList;
    }

    /**
     * 跟新废止状态
     *
     * @param purchaseApprovalList
     */
    @Override
    public void updatePurchaseApprovalBYDelete(PurchaseApprovalList purchaseApprovalList) {
        PurchaseApprovalList purchaseApprovalList1 = baseMapper.selectById(purchaseApprovalList.getId());
        purchaseApprovalList1.setDeleteStatus(Constants.TWO_STR);
        baseMapper.updateById(purchaseApprovalList1);
    }

    @Override
    public void addPurchaseDetail(PurchaseApprovalList purchaseApprovalList1) {
        PurchaseApprovalList purchaseApprovalList = baseMapper.selectById(purchaseApprovalList1.getId());
        if (!purchaseApprovalList.getSpStatus().equals(Constants.TWO_STR)) {
            throw new ServiceException(PurchaseErrorCode.ONLY_ORDER_USING.getCode(), PurchaseErrorCode.ONLY_ORDER_USING.getMsg());
        }
        /**
         * 此过程生成订单详情
         */
        Map<String, String> nodeKeyMap = null;
        ResultBody<List<BpmProcessInstanceStatus>> resultBody = camundaApi.queryProcessInstanceStatus(Arrays.asList(purchaseApprovalList.getId()));
        if (resultBody != null && CollectionUtils.isNotEmpty(resultBody.getData())) {
            nodeKeyMap = resultBody.getData().stream().collect(Collectors.toMap(BpmProcessInstanceStatus::getBusinessKey, BpmProcessInstanceStatus::getNodeKey, (s1, s2) -> s1));
        }
        if (nodeKeyMap != null && !nodeKeyMap.get(purchaseApprovalList.getId()).equals(FINISH_NODE_KEY)) {
            throw new ServiceException(PurchaseErrorCode.NOT_APPROVE_NO_ENDING.getCode(), PurchaseErrorCode.NOT_APPROVE_NO_ENDING.getMsg());
        }
        //采购订单 流程无关联合同
//            GPurchaseContracts one = purchaseContractsService.getOne(Wrappers.<GPurchaseContracts>lambdaQuery().eq(GPurchaseContracts::getApproveId, purchaseApprovalList.getId()));
        PurchaseOrderDetails purchaseOrderDetails = new PurchaseOrderDetails();
        purchaseOrderDetails.setPurchaseOrderNumber(purchaseApprovalList.getNumber());
//            purchaseOrderDetails.setContractNumber(one.getContractNumber());
        purchaseOrderDetails.setProjectName(purchaseApprovalList.getProjectName());
        purchaseOrderDetails.setOrderStatus(Constants.ONE_STR);
        purchaseOrderDetails.setApplicant(purchaseApprovalList.getApplicant());
        purchaseOrderDetails.setApplicantId(purchaseApprovalList.getApplicantId());
        purchaseOrderDetails.setDeptId(purchaseApprovalList.getDeptId());
        purchaseOrderDetails.setDeptName(purchaseApprovalList.getDeptName());
        purchaseOrderDetails.setApplicationTime(purchaseApprovalList.getApplyTime());
        purchaseOrderDetails.setPayStatus(Constants.TWO_STR);
        purchaseOrderDetailsMapper.insert(purchaseOrderDetails);
        if (CollectionUtils.isNotEmpty(purchaseApprovalList.getPurchaseApprovalSupplierList())) {
            for (PurchaseApprovalSupplier purchaseApprovalSupplier : purchaseApprovalList.getPurchaseApprovalSupplierList()) {
                PurchaseOrderDetailSupplier purchaseOrderDetailSupplier = new PurchaseOrderDetailSupplier();
                BeanUtils.copyProperties(purchaseApprovalSupplier, purchaseOrderDetailSupplier);
                purchaseOrderDetailSupplier.setId("");
                purchaseOrderDetailSupplier.setPurchaseDetailId(purchaseOrderDetails.getId());
                purchaseOrderDetailSupplierMapper.insert(purchaseOrderDetailSupplier);
            }
        }
        if (CollectionUtils.isNotEmpty(purchaseApprovalList.getPurchaseApprovalItemsList())) {
            for (PurchaseApprovalItems purchaseApprovalItems : purchaseApprovalList.getPurchaseApprovalItemsList()) {
                PurchaseRelatedProduct purchaseRelatedProduct = new PurchaseRelatedProduct();
                BeanUtils.copyProperties(purchaseApprovalItems, purchaseRelatedProduct);
                purchaseRelatedProduct.setItemName(purchaseApprovalItems.getItemName());
                purchaseRelatedProduct.setDetailId(purchaseOrderDetails.getId());
                purchaseRelatedProductMapper.insert(purchaseRelatedProduct);
            }
        }

    }

    /**
     * 采购呆滞统计
     *
     * @param purchaseDullnessReq
     * @return
     */
    @Override
    public Page<PurchaseApprovalList> dullnessList(PurchaseDullnessReq purchaseDullnessReq) {
        //获取采购订单 节点为采购专员 并且审批时间大于三天
        List<PurchaseOrderDetails> purchaseOrderDetailsList = purchaseOrderDetailsMapper.selectList(Wrappers.<PurchaseOrderDetails>lambdaQuery().select(PurchaseOrderDetails::getId));
        List<PurchaseApprovalList> purchaseApprovalLists = baseMapper.selectList(Wrappers.<PurchaseApprovalList>lambdaQuery().select(PurchaseApprovalList::getId));
        List<String> purchaseOrderDetailIds = purchaseOrderDetailsList.stream().map(PurchaseOrderDetails::getId).collect(Collectors.toList());
        List<String> approvalIds = purchaseApprovalLists.stream().map(PurchaseApprovalList::getId).collect(Collectors.toList());

        List<String> cgzyIdList = new ArrayList<>();
        List<String> cgspIdList = new ArrayList<>();
        List<String> cgspOverIdList = new ArrayList<>();
        //获取订单在专员审批的Id
        if (CollectionUtils.isNotEmpty(purchaseOrderDetailIds)) {
            Map<String, BpmProcessInstanceStatus> processMap = null;
            //获取业务流程状态
            ResultBody<List<BpmProcessInstanceStatus>> resultBody = camundaApi.queryProcessInstanceStatus(purchaseOrderDetailIds);
            if (resultBody != null && CollectionUtils.isNotEmpty(resultBody.getData())) {
                processMap = resultBody.getData().stream().collect(Collectors.toMap(bp -> bp.getBusinessKey(), bp -> bp, (bp1, bp2) -> bp1));
            }
            if (processMap != null) {
                // 获取状态在采购专员的Id
                for (String id : purchaseOrderDetailIds) {
                    if (processMap.get(id) != null) {
                        if (processMap.get(id).getNodeName().contains(nodeName)) {
                            cgzyIdList.add(id);
                        }
                    }
                }
            }

        }
        //获取审批流程处理中的节点
        if (CollectionUtils.isNotEmpty(approvalIds)) {
            Map<String, BpmProcessInstanceStatus> processMap = null;
            //获取业务流程状态
            ResultBody<List<BpmProcessInstanceStatus>> resultBody = camundaApi.queryProcessInstanceStatus(approvalIds);
            if (resultBody != null && CollectionUtils.isNotEmpty(resultBody.getData())) {
                processMap = resultBody.getData().stream().collect(Collectors.toMap(bp -> bp.getBusinessKey(), bp -> bp, (bp1, bp2) -> bp1));
            }
            if (processMap != null) {
                // 获取状态在采购专员的Id
                for (String id : approvalIds) {
                    if (processMap.get(id) != null) {
                        if (processMap.get(id).getResult().equals(Constants.ONE_STR)) {
                            cgspIdList.add(id);
                        }
                        //审批结束
                        if (processMap.get(id).getResult().equals(Constants.TWO_STR)) {
                            cgspOverIdList.add(id);
                        }
                    }
                }
            }
        }

        //
        Page<PurchaseApprovalList> purchaseApprovalListPage = baseMapper.dullnessList(new Page<>(purchaseDullnessReq.getPageNo(), purchaseDullnessReq.getPageSize()), cgzyIdList, cgspIdList, cgspOverIdList, purchaseDullnessReq);

        if (purchaseApprovalListPage.getRecords() != null) {
            Map<String, BpmProcessInstanceStatus> processMap = null;
            List<String> collect = purchaseApprovalListPage.getRecords().stream().map(PurchaseApprovalList::getId).collect(Collectors.toList());
            //获取业务流程状态
            ResultBody<List<BpmProcessInstanceStatus>> resultBody = camundaApi.queryProcessInstanceStatus(collect);
            if (resultBody != null && CollectionUtils.isNotEmpty(resultBody.getData())) {
                processMap = resultBody.getData().stream().collect(Collectors.toMap(bp -> bp.getBusinessKey(), bp -> bp, (bp1, bp2) -> bp1));
            }
            Map<Object, Object> userMap = redisService.hmget(RedisKey.USER_GROUP_TYPE);
            if (processMap != null) {
                for (PurchaseApprovalList purchaseApprovalList : purchaseApprovalListPage.getRecords()) {
                    if (userMap.get(purchaseApprovalList.getApplicant()) != null) {
                        purchaseApprovalList.setApplicant((String) userMap.get(purchaseApprovalList.getApplicant()));
                    }
                    if (processMap.get(purchaseApprovalList.getId()) != null) {
                        if (processMap.get(purchaseApprovalList.getId()).getUserId().indexOf(CommonConstant.SpecialSign.COMMA.getName()) != -1) {
                            String[] userIds = processMap.get(purchaseApprovalList.getId()).getUserId().split(CommonConstant.SpecialSign.COMMA.getName());
                            StringBuilder userName = new StringBuilder();
                            int size = userIds.length;
                            for (int i = 0; i < size; i++) {
                                String name = userMap.get(userIds[i]) == null ? "" : userMap.get(userIds[i]).toString();
                                if (i == size - 1) {
                                    userName.append(name);
                                } else {
                                    userName.append(name).append(CommonConstant.SpecialSign.COMMA.getName());
                                }
                            }
                            purchaseApprovalList.setApproveUserId(processMap.get(purchaseApprovalList.getId()).getUserId());
                            purchaseApprovalList.setApproveUser(userName.toString());
                        } else {
                            purchaseApprovalList.setApproveUserId(processMap.get(purchaseApprovalList.getId()).getUserId());
                            purchaseApprovalList.setApproveUser(userMap.get(processMap.get(purchaseApprovalList.getId()).getUserId()) == null ? "" : userMap.get(processMap.get(purchaseApprovalList.getId()).getUserId()).toString());
                        }
                    }
                }
            }
        }
        //获取所有审批状态为未结束

        return purchaseApprovalListPage;
    }

    /***
     * 获取编号
     * @return
     */

    @Override
    @RedissonLock(key = PURCHASE_APPROVE_NUMBER, prefixKey = "lock_")
    public String getApproveSequenceNumber() {
        String number = "";
        String date = LocalDate.now().format(DateTimeFormatter.ofPattern(CommonConstant.DATE_FORMAT_UN_SEPARATE));
        date = "SY-".concat(date);
        Serializable serializable = redisService.get(PURCHASE_APPROVE_NUMBER);
        if (serializable != null && StringUtils.isNotBlank(serializable.toString())) {
            number = serializable.toString();
        } else {
            number = baseMapper.getSequenceNumber();
        }
        if (StringUtils.isNotBlank(number) && number.length() > 11) {
            String sequence = number.substring(11);
            int sequenceInt = Integer.parseInt(sequence);
            sequenceInt = sequenceInt + 1;
            String newSequence = String.valueOf(sequenceInt);
            if (newSequence.length() == CommonConstant.FIVE_INT) {
                number = date.concat("0001");
            } else {
                String fourDigits = String.format("%04d", sequenceInt); // 格式化数字为4位，不足部分用0填充
                number = date.concat(fourDigits);
            }
        } else {
            number = date.concat("0001");
        }
        redisService.set(PURCHASE_APPROVE_NUMBER, number);
        return number;
    }

    @Override
    public List<PurchaseApprovalList> getProjectNameList() {
        List<PurchaseApprovalList> list = this.list(Wrappers.<PurchaseApprovalList>lambdaQuery()
                .select(PurchaseApprovalList::getId, PurchaseApprovalList::getProjectName,
                        PurchaseApprovalList::getNumber, PurchaseApprovalList::getPurchaseMode)
                .isNotNull(PurchaseApprovalList::getNumber).isNotNull(PurchaseApprovalList::getProjectName)
                .eq(PurchaseApprovalList::getIsFinished, CommonConstant.ONE_STR)
                .orderBy(true, false, PurchaseApprovalList::getNumber)
        );

        if (CollectionUtils.isNotEmpty(list)) {
            List<String> ids = list.stream().map(PurchaseApprovalList::getId).collect(Collectors.toList());
            List<PurchaseApprovalSupplier> suppliers = purchaseApprovalSupplierService.list(
                    Wrappers.<PurchaseApprovalSupplier>lambdaQuery().in(PurchaseApprovalSupplier::getPurchaseApprovalId, ids));
            Map<String, List<PurchaseApprovalSupplier>> supplierMap = null;
            if (CollectionUtils.isNotEmpty(suppliers)) {
                supplierMap = suppliers.stream().collect(Collectors.groupingBy(PurchaseApprovalSupplier::getPurchaseApprovalId));
            }

            List<PurchaseApprovalItems> items = purchaseApprovalItemsService.list(
                    Wrappers.<PurchaseApprovalItems>lambdaQuery().in(PurchaseApprovalItems::getPurchaseApprovalId, ids));
            Map<String, List<PurchaseApprovalItems>> itemMap = null;
            if (CollectionUtils.isNotEmpty(items)) {
                itemMap = items.stream().collect(Collectors.groupingBy(PurchaseApprovalItems::getPurchaseApprovalId));
            }

            for (PurchaseApprovalList approvalList : list) {
                if (supplierMap != null) {
                    approvalList.setPurchaseApprovalItemsList(itemMap.get(approvalList.getId()));
                }
                if (supplierMap != null) {
                    approvalList.setPurchaseApprovalSupplierList(supplierMap.get(approvalList.getId()));
                }
            }
        }

        return list;
    }

    @Override
    public List<PurchaseApprovalList> getContractsProject() {
        List<PurchaseApprovalList> list = this.list(Wrappers.<PurchaseApprovalList>lambdaQuery()
                .select(PurchaseApprovalList::getId, PurchaseApprovalList::getProjectName,
                        PurchaseApprovalList::getNumber, PurchaseApprovalList::getPurchaseMode)
                .isNotNull(PurchaseApprovalList::getNumber).isNotNull(PurchaseApprovalList::getProjectName)
                .eq(PurchaseApprovalList::getIsFinished, CommonConstant.ONE_STR)
                .eq(PurchaseApprovalList::getIsUsed, CommonConstant.ZERO_STR)
                .eq(PurchaseApprovalList::getSpStatus, CommonConstant.ONE_STR)
                .orderByDesc(PurchaseApprovalList::getCreateTime)
        );

        return list;
    }

    @Override
    public List<PurchaseApprovalList> getFrameContractsProject() {
        return baseMapper.getFrameContractsProject();
    }

    @Override
    public List<PurchaseApprovalList> getReportProject() {
        List<String> params = new ArrayList<>();
        params.add(CommonConstant.ONE_STR);
        params.add(CommonConstant.THREE_STR);
        List<PurchaseApprovalList> list = this.list(Wrappers.<PurchaseApprovalList>lambdaQuery()
                .select(PurchaseApprovalList::getId, PurchaseApprovalList::getProjectName,
                        PurchaseApprovalList::getNumber, PurchaseApprovalList::getPurchaseMode,
                        PurchaseApprovalList::getSpStatus)
                .isNotNull(PurchaseApprovalList::getNumber).isNotNull(PurchaseApprovalList::getProjectName)
                .eq(PurchaseApprovalList::getIsFinished, CommonConstant.ONE_STR)
                .eq(PurchaseApprovalList::getIsReportUsed, CommonConstant.ZERO_STR)
                .in(PurchaseApprovalList::getSpStatus, params)
                .orderByDesc(PurchaseApprovalList::getCreateTime)
        );

        List<PurchaseApprovalList> total = new ArrayList<>();
        List<PurchaseApprovalList> orderProjects = list.stream().filter(pa -> CommonConstant.ONE_STR.equals(pa.getSpStatus())).collect(Collectors.toList());
        total.addAll(orderProjects);
        List<PurchaseApprovalList> frameProjects = list.stream().filter(pa -> CommonConstant.THREE_STR.equals(pa.getSpStatus())).collect(Collectors.toList());
        if (CollectionUtils.isNotEmpty(frameProjects)) {
            List<String> ids = frameProjects.stream().map(fp -> fp.getId()).collect(Collectors.toList());
            List<PurchaseApprovalItems> items = purchaseApprovalItemsService.list(Wrappers.<PurchaseApprovalItems>lambdaQuery().in(PurchaseApprovalItems::getPurchaseApprovalId, ids));
            Map<String, List<PurchaseApprovalItems>> itemMap = null;
            if (CollectionUtils.isNotEmpty(items)) {
                itemMap = items.stream().collect(Collectors.groupingBy(PurchaseApprovalItems::getPurchaseApprovalId));
            }
            for (PurchaseApprovalList frameProject : frameProjects) {
                if (CollectionUtils.isNotEmpty(itemMap.get(frameProject.getId()))) {
                    total.add(frameProject);
                }
            }
        }
        return total;
    }


    public static void main(String[] args) {
        String number = "SY-202304031764";
        System.out.println(number.substring(11));
    }
}
